#include <func.h>
#include <openssl/md5.h>
#define MAXKEY 1000
#define MD5_SIZE 16
#define MD5_STR_LEN (MD5_SIZE * 2)
enum e_command
{
    CMD_CD,     // 进入对应目录
    CMD_LS,     // 列出相应目录文件
    CMD_PUTS,   // 上传本地文件至服务器
    CMD_GETS,   // 从服务器下载文件到本地
    CMD_REMOVE, // 删除服务器上的文件
    CMD_PWD,    // 显示当前所在路径
    CMD_MKDIR,  // 创建文件夹
    CMD_LOGIN,  // 用户登录
    CMD_SIGNUP  // 用户注册
};

typedef struct cmd_s
{
    char object[256]; // 命令的操作对象
    int token;        // 命令类型
    off_t offset;     // 已传文件大小
} cmd_t;

typedef struct CmdWord
{ // 存储命令与其对应枚举值
    char str[100];
    int token;
} CmdWord, *pCmdWord;

typedef struct train_s
{
    int length;
    char data[1000];
} train_t;

static CmdWord cmdword[] = {
    {"cd", CMD_CD},
    {"ls", CMD_LS},
    {"puts", CMD_PUTS},
    {"gets", CMD_GETS},
    {"remove", CMD_REMOVE},
    {"pwd", CMD_PWD},
    {"mkdir", CMD_MKDIR}};

extern pCmdWord HashTable[MAXKEY];

int tcpInit(char *config_file, int *psockfd);
int recvn(int netfd, void *buf, int length);
int recvFile(int netfd, off_t offset);
int elf_hash(char *key);
int init_hash(pCmdWord cmdword, int cmdword_length);
int cmd_anal(const char *buf, int buf_length, cmd_t *pCmd);
int transFile(int sockfd, cmd_t Cmd);
void user_login(int sockfd, char *user_name);
void clean_stdin();
int isunfinished(cmd_t Cmd);
off_t get_offset(char *fileName);
int Compute_file_md5(char *file_path, char *md5_str);
